﻿#ifndef GL_ITEM_H_
#define GL_ITEM_H_

#include <QOpenGLFunctions>
#include <QVector3D>
#include <QColor>
#include <QVector>
#include <QMatrix4x4>


enum {
    GLItem_None,
    GLItem_Line,
    GLItem_Triangle,
    GLItem_Rect,
    GLItem_Box,
    GLItem_Text,
    GLItem_Mesh,
};

enum GLDrawType{
    GLDraw_Mesh,
    GLDraw_Line,
    GLDraw_2D,
};

class VertexData
{
public:
    VertexData();

    QVector3D pos;
    QColor color;
};

class JZGLScene;
/*
欧拉数万向锁是一次旋转3个角度，中间的角度如果是90度，等于先旋转的坐标重合了。
m_model.rotate 
*/
class JZGLItem
{
public:
    static void worldToLocal(const QVector<QVector3D>& pt_list, QVector3D& pos, QVector<QVector3D>& local_list);

    JZGLItem();
    virtual ~JZGLItem();

    int type() const;

    void setParent(JZGLItem* parent);
    JZGLItem* parent();

    QVector3D position();
    void setPosition(QVector3D pos);

    void setDrawType(GLDrawType type);
    GLDrawType drawType();

    QList<JZGLItem*> childItems() const;
    void addChild(JZGLItem *item);
    void removeChild(JZGLItem* item);

    void update();

    bool isVisible() const;
    void setVisible(bool flag);
        
    JZGLScene *scene();
    void setScene(JZGLScene *scene);

    QMatrix4x4 model() const;
    void setModel(QMatrix4x4 m);
    void resetModel();
    
    void scale(float x, float y, float z);
    void rotate(float angle, float x, float y, float z);
    void translate(float x, float y, float z);

    virtual void setColor(QColor c);
    virtual void setVertexColor(int index,QColor c);

    VertexData vertex(int index);
    void setVertex(int index, VertexData pt);
    void setVertexList(const QVector<VertexData>& points);
    
    virtual void updateBuffer();
    virtual void paint(QPainter *painter);

protected:
    Q_DISABLE_COPY(JZGLItem);

    QVector<int> meshIndexToLineIndex(const QVector<int>& index_list);
    void addLineVertex(const QVector<VertexData>& pt_list,const QVector<int>& index_list);
    void addMeshVertex(const QVector<VertexData>& pt_list, const QVector<int>& index_list);

    int m_type;
    GLDrawType m_drawType;    
    QVector<VertexData> m_points;
    JZGLScene* m_scene;
    JZGLItem* m_parent;
    QList<JZGLItem*> m_childItems;
    bool m_visible;

    QVector3D m_position;
    QMatrix4x4 m_model;
};

class JZGLLineItem : public JZGLItem
{
public:
    JZGLLineItem();
    void setLine(VertexData p1, VertexData p2);

    virtual void updateBuffer() override;
};

class JZGLTriangleItem : public JZGLItem
{
public:
    JZGLTriangleItem();
    void setTriangle(VertexData p1, VertexData p2, VertexData p3);

    virtual void updateBuffer() override;
};

class JZGLRectItem : public JZGLItem
{
public:
    JZGLRectItem();
    void setRect(float w, float h, QColor c);
    void setRect(const QVector<VertexData> &vertex_list);

    virtual void updateBuffer() override;
};

class JZGLBoxItem : public JZGLItem
{
public:
    JZGLBoxItem();
    void setBox(float w, float h, float depth,QColor c);
    void setBox(const QVector<VertexData>& vertex_list);

    virtual void updateBuffer() override;
};

class JZGLTextItem : public JZGLItem
{
public:
    JZGLTextItem();

    void setText(QString text);
    virtual void paint(QPainter* painter) override;
    virtual void setColor(QColor c);

protected:
    QString m_text;
    QColor m_color;
};

class JZGLMeshItem : public JZGLItem
{
public:
    JZGLMeshItem();
};

#endif // !GL_ITEM_H_
